/* Copyright (c) 2025 Beijing Semidrive Technology Corporation
 * SPDX-License-Identifier: Apache-2.0
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
/** ************************************************************************************************
 * @file     sdrv_awic_lld.h                                                                       *
 * @brief    This file contains interface header for AWIC LLD driver.                              *
 * @author   Department/Semidrive                                                                  *
 * @date     2024/11/26                                                                            *
 *                                                                                                 *
 **************************************************************************************************/

#ifndef SDRV_AWIC_LLD_H
#define SDRV_AWIC_LLD_H

#include <stdint.h>
#include <debug.h>
#include <stdbool.h>

#include <reg.h>
#include <regs_base.h>

#ifdef __cplusplus
extern "C" {
#endif

#if (CONFIG_WITH_AWIC_DEBUG) && (CONFIG_PRINTF_LIB)
#include <debug.h>
#define AWIC_LOG_DEBUG(x...) ssdk_printf(SSDK_DEBUG,x)
#define AWIC_LOG_ERROR(x...) ssdk_printf(SSDK_ERR,x)
#elif (CONFIG_WITH_AWIC_DEBUG) && defined(AUTOSAR_OS_NOT_USED)
#include <debug.h>
#define AWIC_LOG_DEBUG(x...) PRINT(x)
#define AWIC_LOG_ERROR(x...) PRINT(x)
#else
#define AWIC_LOG_DEBUG(...)
#define AWIC_LOG_ERROR(...)
#endif

/***************************************************************************************************
 *                                 Global Macro definition
 **************************************************************************************************/

#define AWIC_PAD_INDEX_NUM              (23U)

#define AWIC_BIT(nr)                    ((uint32_t)1u << (nr))

#define AWIC_RET_OK                     (0)
#define AWIC_RET_FAILED                 (-1)
#define AWIC_RET_PARAMETER_ERR          (-2)

/***************************************************************************************************
 *                                  Global Types definition                                        *
 **************************************************************************************************/

/** \brief AWIC BIT control type */
typedef enum {
    AWIC_BIT_CTRL_INT_TYPE_LEVEL_HIGH   = 0U,
    AWIC_BIT_CTRL_INT_TYPE_LEVEL_LOW    = 1U,
    AWIC_BIT_CTRL_INT_TYPE_RISING_EDGE  = 2U,
    AWIC_BIT_CTRL_INT_TYPE_FALLING_EDGE = 3U,
    AWIC_BIT_CTRL_INT_TYPE_TOGGLE       = 4U,
    AWIC_BIT_CTRL_INT_TYPE_MAX          = 5U,
} Awic_PadIntDetectType;

/** \brief AWIC PAD Direction  */
typedef enum {
    AWIC_PAD_DIRECTION_INPUT        = 0U,
    AWIC_PAD_DIRECTION_OUTPUT       = 1U,
} Awic_PadDirectionType;

/***************************************************************************************************
 *                                  Global Function Declarations                                   *
 **************************************************************************************************/

/**
 * @brief sdrv awic read reg.
 *
 * @param [in] base reg base
 * @param [in] offset reg offset
 * @param [in] return reg val
 */
static inline uint32_t sdrv_awic_hw_readl(uint32_t base, uint32_t offset)
{
    return readl(base + offset);
}

/**
 * @brief sdrv awic write reg.
 *
 * @param [in] base reg base
 * @param [in] offset reg offset
 * @param [in] val reg val
 */
static inline void sdrv_awic_hw_writel(uint32_t base, uint32_t offset, uint32_t val)
{
    writel(val, (base + offset));
}

/**
 * @brief AWIC pad value and direction configure.
 *
 * @param [in] base device base.
 * @param [in] index pad index  0-22 represents GPIO_LP.IO0-GPIO_LP.IO22 .
 * @param [in] dir pad direction override value.
 * @param [in] val pad output data override value.
 * @return AWIC_RET_OK success, otherwise failed.
 */
int awic_lld_pad_value_config(uint32_t base, uint32_t index, Awic_PadDirectionType dir, uint8_t val);


/**
 * @brief AWIC pad sync interrupt unmask.
 *
 * @param [in] base device base.
 * @param [in] enable true or false.
 */
void awic_lld_pad_sync_int_unmask(uint32_t base, bool enable);

/**
 * @brief AWIC pad async interrupt unmask.
 *
 * @param [in] base device base.
 * @param [in] enable true or false.
 */
void awic_lld_pad_async_int_unmask(uint32_t base, bool enable);

/**
 * @brief AWIC pad sync interrupt clear.
 *
 * @param [in] base device base.
 */
void awic_lld_pad_sync_int_clr(uint32_t base);

/**
 * @brief AWIC pad async interrupt clear.
 *
 * @param [in] base device base.
 */
void awic_lld_pad_async_int_clr(uint32_t base);

/**
 * @brief AWIC pad sync interrupt status get.
 *
 * @param [in] base device base.
 * @return sync interrupt status.
 */
uint32_t awic_lld_pad_sync_int_sta_get(uint32_t base);

/**
 * @brief AWIC pad async interrupt status get.
 *
 * @param [in] base device base.
 * @return async interrupt status.
 */
uint32_t awic_lld_pad_async_int_sta_get(uint32_t base);

/**
 * @brief AWIC force override enable.
 *
 * @param [in] base device base.
 * @param [in] enable true or false.
 */
void awic_lld_force_override_en(uint32_t base, bool enable);

/**
 * @brief AWIC sync interrupt snapshot enable.
 *
 * @param [in] base device base.
 * @param [in] enable true or false.
 */
void awic_lld_sync_int_snap_en(uint32_t base, bool enable);

/**
 * @brief AWIC async interrupt snapshot enable.
 *
 * @param [in] base device base.
 * @param [in] enable true or false.
 */
void awic_lld_async_int_snap_en(uint32_t base, bool enable);

/**
 * @brief AWIC module enable.
 *
 * @param [in] base device base.
 * @param [in] enable true or false.
 */
void awic_lld_module_en(uint32_t base, bool enable);

/**
 * @brief AWIC first sync wakeup source get.
 *
 * @param [in] base device base.
 * @return sync interrupt snapshot.
 */
uint32_t awic_lld_sync_first_wakeup_src_get(uint32_t base);

/**
 * @brief AWIC first async wakeup source get.
 *
 * @param [in] base device base.
 * @return async interrupt snapshot.
 */
uint32_t awic_lld_async_first_wakeup_src_get(uint32_t base);

/**
 * @brief AWIC sync wakeup source get.
 *
 * @param [in] base device base.
 * @return sync interrupt wakeup source.
 */
uint32_t awic_lld_sync_wakeup_src_get(uint32_t base);

/**
 * @brief AWIC async wakeup source get.
 *
 * @param [in] base device base.
 * @return async interrupt wakeup source.
 */
uint32_t awic_lld_async_wakeup_src_get(uint32_t base);

/**
 * @brief AWIC pad sync interrupt configure.
 *
 * @param [in] base device base.
 * @param [in] index pad index  0-22 represents GPIO_LP.IO0-GPIO_LP.IO22 .
 * @param [in] type pad interrupt detect type.
 * @param [in] enable pad interrupt enable.
 * @return AWIC_RET_OK success, otherwise failed.
 */
int awic_lld_pad_sync_int_config(uint32_t base, uint32_t index, Awic_PadIntDetectType type, bool enable);

/**
 * @brief AWIC pad async interrupt configure.
 *
 * @param [in] base device base.
 * @param [in] index pad index  0-22 represents GPIO_LP.IO0-GPIO_LP.IO22 .
 * @param [in] type pad interrupt detect type.
 * @param [in] enable pad interrupt enable.
 * @return AWIC_RET_OK success, otherwise failed.
 */
int awic_lld_pad_async_int_config(uint32_t base, uint32_t index, Awic_PadIntDetectType type, bool enable);

/**
 * @brief AWIC override by swm state enable.
 *        After entering RTC mode, pad override enable.
 *        The pad is restored to its original value after waking up.
 *
 * @param [in] base device base.
 * @param [in] enable true or false.
 */
void awic_lld_override_by_swm_en(uint32_t base, bool enable);

#ifdef __cplusplus
}
#endif
#endif /* SDRV_AWIC_LLD_H */

/* End of file */
